package com.cskaoyan.java.object._6clone.depth;

/**
 * 深度克隆
 *
 * Object类当中的clone方法实现是一个浅克隆
 * 所谓的浅克隆指的是:
 *      1.对象中的基本数据类型成员变量,直接拷贝一份到新的对象中
 *      2.对象中的引用数据类型成员变量存的是引用
 *          这时直接拷贝一份引用到新的对象中
 * 由于浅克隆只会拷贝一份引用,这时原先对象和克隆对象仍然是有关联的,还是会互相影响的
 *
 * 为了让克隆得到一个新的独立的对象,需要进行深度克隆操作
 * 深度克隆的操作步骤如下:
 *      0.深度克隆是在浅克隆的基础上进行
 *      1.将对象中拷贝引用指向的对象克隆一份
 *      2.让克隆引用指向克隆对象
 *
 *
 * @since 17:33
 * @author wuguidong@cskaoyan.onaliyun.com
 */
public class Demo {
    public static void main(String[] args) throws CloneNotSupportedException {
        Student s = new Student(new Star(10000), 20);
        Student cloneStu = s.clone();
        s.age = 30;
        System.out.println(cloneStu.age);
        s.star.salary = 20000;
        System.out.println(cloneStu.star.salary);
    }
}

class Student implements Cloneable {
    Star star;
    int age;

    public Student(Star star, int age) {
        this.star = star;
        this.age = age;
    }

    // 对Student类进行深度克隆操作,需要修改Student类的clone方法实现
    @Override
    protected Student clone() throws CloneNotSupportedException {
        // 0.深度克隆是在浅克隆的基础上进行
        Student cloneStu = (Student) super.clone();
        // 1.将对象中拷贝引用指向的对象克隆一份
        // 这里需要克隆Star对象
        Star cloneStar = star.clone();
        // 2.让克隆引用指向克隆对象
        cloneStu.star = cloneStar;
        return cloneStu;
    }
}

class Star implements Cloneable {
    double salary;

    public Star(double salary) {
        this.salary = salary;
    }

    @Override
    protected Star clone() throws CloneNotSupportedException {
        return (Star) super.clone();
    }
}